<?php
/**
 * Acl角色
 *
 * @since 0.1
 * @package net.4kiki.acl
 */
class IAclRole extends IObject {
	private $name;
	private $allows = array();
	private $denies = array();
	
	/**
	 * 构造器
	 *
	 * @param string $name 角色名
	 * @since 0.1
	 */
	public function __construct($name) {
		$this->name = $name;
	}
	
	/**
	 * 取得名称
	 *
	 * @return string
	 * @since 0.1
	 */
	public function getName() {
		return $this->name;
	}
	
	/**
	 * 添加允许访问的资源
	 *
	 * @param IAclResource $resource 资源
	 * @since 0.1
	 */
	public function allow(IAclResource $resource) {
		$this->allows[$resource->getName()] = $resource;
	}
	
	/**
	 * 添加禁止访问的资源
	 *
	 * @param IAclResource $resource 资源
	 * @since 0.1
	 */
	public function deny(IAclResource $resource) {
		$this->denies[$resource->getName()] = $resource;
	}
	
	/**
	 * 判断资源是否被允许访问
	 *
	 * @param IAclResource $resource 资源
	 * @return boolean
	 * @since 0.1
	 */
	public function isAllowed(IAclResource $resource) {
		$name = $resource->getName();
		if (array_key_exists($name, $this->denies)) {
			return false;
		}
		if (array_key_exists($name, $this->allows)) {
			return true;
		}
		return false;
	}
	
	/**
	 * 取得允许的资源
	 *
	 * @return array
	 * @since 0.1
	 */
	public function getAllows() {
		foreach ($this->allows as $name=>$allow) {
			if (array_key_exists($name, $this->denies)) {
				unset($this->allows[$name]);
			}
		}
		return $this->allows;
	}
	
	/**
	 * 取得禁止的资源
	 *
	 * @return array
	 * @since 0.1
	 */
	public function getDenies() {
		return $this->denies;
	}
	
	/**
	 * 继承别的角色
	 *
	 * @param IAclRole $parent 被继承的角色
	 * @since 0.1
	 */
	public function extend(IAclRole $parent) {
		foreach ($parent->getAllows() as $resource) {
			if (!array_key_exists($resource->getName(), $this->allows) && !array_key_exists($resource->getName(), $this->denies)) {
				$this->allow($resource);
			}
		}
		foreach ($parent->getDenies() as $resource) {
			if (!array_key_exists($resource->getName(), $this->allows) && !array_key_exists($resource->getName(), $this->denies)) {
				$this->deny($resource);
			}
		}		
	}
}

?>